<!doctype html>
<html lang="zh-Hans" dir="ltr" class="docs-wrapper docs-doc-page docs-version-current plugin-docs plugin-id-default docs-doc-id-action/springfox/springfox5">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<meta name="generator" content="Docusaurus v2.0.1">
<link rel="search" type="application/opensearchdescription+xml" title="Knife4j" href="/opensearch.xml">

<!-- Google Tag Manager -->
    <script>!function(e,t,a,n,g){e[n]=e[n]||[],e[n].push({"gtm.start":(new Date).getTime(),event:"gtm.js"});var m=t.getElementsByTagName(a)[0],r=t.createElement(a);r.async=!0,r.src="https://www.googletagmanager.com/gtm.js?id=GTM-TKBX678",m.parentNode.insertBefore(r,m)}(window,document,"script","dataLayer")</script>
    <!-- End Google Tag Manager -->
<script src="/js/custom.js"></script>
<script src="/js/baidu.js"></script>
<script src="https://pagead2.googlesyndication.com/pagead/js/adsbygoogle.js?client=ca-pub-1589206801610969" async crossorigin="anonymous"></script><title data-rh="true">springfox 源码分析(五) web配置类Plugin插件的使用 | Knife4j</title><meta data-rh="true" name="twitter:card" content="summary_large_image"><meta data-rh="true" property="og:url" content="https://doc.xiaominfo.com/docs/action/springfox/springfox5"><meta data-rh="true" name="docusaurus_locale" content="zh-Hans"><meta data-rh="true" name="docsearch:language" content="zh-Hans"><meta data-rh="true" name="docusaurus_version" content="current"><meta data-rh="true" name="docusaurus_tag" content="docs-default-current"><meta data-rh="true" name="docsearch:version" content="current"><meta data-rh="true" name="docsearch:docusaurus_tag" content="docs-default-current"><meta data-rh="true" property="og:title" content="springfox 源码分析(五) web配置类Plugin插件的使用 | Knife4j"><meta data-rh="true" name="description" content="时间：2019-5-23 1450"><meta data-rh="true" property="og:description" content="时间：2019-5-23 1450"><link data-rh="true" rel="icon" href="/img/favicon.ico"><link data-rh="true" rel="canonical" href="https://doc.xiaominfo.com/docs/action/springfox/springfox5"><link data-rh="true" rel="alternate" href="https://doc.xiaominfo.com/docs/action/springfox/springfox5" hreflang="zh-Hans"><link data-rh="true" rel="alternate" href="https://doc.xiaominfo.com/docs/action/springfox/springfox5" hreflang="x-default"><link data-rh="true" rel="preconnect" href="https://3CRIMRK623-dsn.algolia.net" crossorigin="anonymous"><link rel="stylesheet" href="/assets/css/styles.66359a73.css">
<link rel="preload" href="/assets/js/runtime~main.e0db172c.js" as="script">
<link rel="preload" href="/assets/js/main.c059fb6e.js" as="script">
</head>
<body class="navigation-with-keyboard">
<script>!function(){function e(e){document.documentElement.setAttribute("data-theme",e)}var t=function(){var e=null;try{e=localStorage.getItem("theme")}catch(e){}return e}();null!==t?e(t):window.matchMedia("(prefers-color-scheme: dark)").matches?e("dark"):window.matchMedia("(prefers-color-scheme: light)").matches?e("light"):e("dark")}()</script><div id="__docusaurus">
<div role="region"><a href="#" class="skipToContent_fXgn">跳到主要内容</a></div><nav class="navbar navbar--fixed-top navbarHideable_m1mJ"><div class="navbar__inner"><div class="navbar__items"><button aria-label="Navigation bar toggle" class="navbar__toggle clean-btn" type="button" tabindex="0"><svg width="30" height="30" viewBox="0 0 30 30" aria-hidden="true"><path stroke="currentColor" stroke-linecap="round" stroke-miterlimit="10" stroke-width="2" d="M4 7h22M4 15h22M4 23h22"></path></svg></button><a class="navbar__brand" href="/"><div class="navbar__logo"><img src="/img/knife4j-light.svg" alt="" class="themedImage_ToTc themedImage--light_HNdA"><img src="/img/knife4j-dark.svg" alt="" class="themedImage_ToTc themedImage--dark_i4oU"></div><b class="navbar__title text--truncate">Knife4j</b></a><a class="navbar__item navbar__link" href="/docs/quick-start">文档</a><a class="navbar__item navbar__link changelog" href="/docs/middleware-sources">中间件</a><a class="navbar__item navbar__link changelog" href="/docs/oas">OAS规范</a><a aria-current="page" class="navbar__item navbar__link changelog navbar__link--active" href="/docs/action">实战指南</a><a class="navbar__item navbar__link changelog" href="/docs/changelog">更新日志</a><a class="navbar__item navbar__link changelog" href="/docs/faq">FAQ</a><div class="navbar__item dropdown dropdown--hoverable"><a href="#" aria-haspopup="true" aria-expanded="false" role="button" class="navbar__link">旧版本</a><ul class="dropdown__menu"><li><a class="dropdown__link" target="_blank" href="/v2/index.html">2.0.9</a></li></ul></div></div><div class="navbar__items navbar__items--right"><div class="toggle_MW0i colorModeToggle_x44X"><button class="clean-btn toggleButton_yw5v toggleButtonDisabled_BJd7" type="button" disabled="" title="切换浅色/暗黑模式（当前为暗黑模式）" aria-label="切换浅色/暗黑模式（当前为暗黑模式）"><span><svg viewBox="0 0 13 12" fill="none" xmlns="http://www.w3.org/2000/svg" width="14" height="14" class="lightToggleIcon_SFTY"><g clip-path="url(#clip0_833_8168)"><path d="M6.59998 8.49999C7.98069 8.49999 9.09998 7.3807 9.09998 5.99999C9.09998 4.61928 7.98069 3.49999 6.59998 3.49999C5.21926 3.49999 4.09998 4.61928 4.09998 5.99999C4.09998 7.3807 5.21926 8.49999 6.59998 8.49999Z" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round"></path><path d="M6.59985 0.5V1.5" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round"></path><path d="M6.59985 10.5V11.5" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round"></path><path d="M2.7099 2.11L3.4199 2.82" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round"></path><path d="M9.77991 9.17999L10.4899 9.88999" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round"></path><path d="M1.09998 6H2.09998" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round"></path><path d="M11.0999 6H12.0999" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round"></path><path d="M2.7099 9.88999L3.4199 9.17999" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round"></path><path d="M9.77991 2.82L10.4899 2.11" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round"></path></g><defs><clipPath id="clip0_833_8168"><rect width="12" height="12" fill="white" transform="translate(0.599976)"></rect></clipPath></defs></svg><svg viewBox="0 0 13 12" width="14" height="14" class="darkToggleIcon_ekgs"><path d="M10.7001 6.39501C10.6215 7.24611 10.3021 8.05721 9.77927 8.7334C9.25646 9.40959 8.55189 9.92291 7.748 10.2133C6.9441 10.5036 6.07414 10.5591 5.2399 10.3731C4.40565 10.187 3.64164 9.76728 3.03726 9.1629C2.43287 8.55851 2.01312 7.7945 1.8271 6.96026C1.64108 6.12602 1.6965 5.25605 1.98688 4.45216C2.27725 3.64826 2.79056 2.94369 3.46675 2.42088C4.14294 1.89808 4.95404 1.57866 5.80515 1.50001C5.30685 2.17414 5.06707 3.00473 5.12941 3.84071C5.19175 4.6767 5.55208 5.46254 6.14485 6.05531C6.73762 6.64808 7.52346 7.0084 8.35944 7.07074C9.19542 7.13308 10.026 6.8933 10.7001 6.39501Z" stroke="currentColor" fill="transparent" stroke-linecap="round" stroke-linejoin="round"></path></svg></span></button></div><a href="https://github.com/xiaoymin/swagger-bootstrap-ui" target="_blank" rel="noopener noreferrer" class="navbar__item navbar__link icon" title="View on GitHub">GitHub<svg width="13.5" height="13.5" aria-hidden="true" viewBox="0 0 24 24" class="iconExternalLink_nPIU"><path fill="currentColor" d="M21 13v10h-21v-19h12v2h-10v15h17v-8h2zm3-12h-10.988l4.035 4-6.977 7.07 2.828 2.828 6.977-7.07 4.125 4.172v-11z"></path></svg></a><div class="searchBox_ZlJk"><button type="button" class="DocSearch DocSearch-Button" aria-label="搜索"><span class="DocSearch-Button-Container"><svg width="20" height="20" class="DocSearch-Search-Icon" viewBox="0 0 20 20"><path d="M14.386 14.386l4.0877 4.0877-4.0877-4.0877c-2.9418 2.9419-7.7115 2.9419-10.6533 0-2.9419-2.9418-2.9419-7.7115 0-10.6533 2.9418-2.9419 7.7115-2.9419 10.6533 0 2.9419 2.9418 2.9419 7.7115 0 10.6533z" stroke="currentColor" fill="none" fill-rule="evenodd" stroke-linecap="round" stroke-linejoin="round"></path></svg><span class="DocSearch-Button-Placeholder">搜索</span></span><span class="DocSearch-Button-Keys"></span></button></div></div></div><div role="presentation" class="navbar-sidebar__backdrop"></div></nav><div class="main-wrapper mainWrapper_z2l0 docsWrapper_BCFX"><button aria-label="回到顶部" class="clean-btn theme-back-to-top-button backToTopButton_sjWU" type="button"></button><div class="docPage__5DB"><aside class="theme-doc-sidebar-container docSidebarContainer_b6E3"><div class="sidebar_njMd sidebarWithHideableNavbar_wUlq"><a tabindex="-1" class="sidebarLogo_isFc" href="/"><img src="/img/knife4j-light.svg" alt="" class="themedImage_ToTc themedImage--light_HNdA"><img src="/img/knife4j-dark.svg" alt="" class="themedImage_ToTc themedImage--dark_i4oU"><b>Knife4j</b></a><nav class="menu thin-scrollbar menu_SIkG"><ul class="theme-doc-sidebar-menu menu__list"><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-1 menuHtmlItem_M9Kj menu__list-item">
<div class="sidebar_donate">
    <div class="sidebar_sponsor">
        <a target="_blank" href="https://www.apifox.com/apiskills/apifox-auto-generates-api-docs/?utm_source=pay&utm_medium=knife4jg"><img src="/images/sponsor/apifox/Apifox IDEA@3x.png">
        </a>
    </div>
    <div class="sidebar_sponsor_submit">
        <a href="/docs/community/donate">成为赞助商</a>
    </div>
<div>
</div></div></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-1 menu__list-item"><a class="menu__link" href="/docs/action">实战指南</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-1 menu__list-item"><a class="menu__link" href="/docs/action/action-simple">示例代码</a></li><li class="theme-doc-sidebar-item-category theme-doc-sidebar-item-category-level-1 menu__list-item menu__list-item--collapsed"><div class="menu__list-item-collapsible"><a class="menu__link menu__link--sublist menu__link--sublist-caret" aria-expanded="false" href="/docs/action/mavenbom">Spring 单体架构</a></div></li><li class="theme-doc-sidebar-item-category theme-doc-sidebar-item-category-level-1 menu__list-item menu__list-item--collapsed"><div class="menu__list-item-collapsible"><a class="menu__link menu__link--sublist menu__link--sublist-caret" aria-expanded="false" href="/docs/action/springcloud-gateway">Spring微服务架构</a></div></li><li class="theme-doc-sidebar-item-category theme-doc-sidebar-item-category-level-1 menu__list-item menu__list-item--collapsed"><div class="menu__list-item-collapsible"><a class="menu__link menu__link--sublist menu__link--sublist-caret" aria-expanded="false" href="/docs/action/oauth2-implicit">OAuth2.0</a></div></li><li class="theme-doc-sidebar-item-category theme-doc-sidebar-item-category-level-1 menu__list-item menu__list-item--collapsed"><div class="menu__list-item-collapsible"><a class="menu__link menu__link--sublist menu__link--sublist-caret" aria-expanded="false" href="/docs/action/aggregation-disk">微服务聚合实战</a></div></li><li class="theme-doc-sidebar-item-category theme-doc-sidebar-item-category-level-1 menu__list-item menu__list-item--collapsed"><div class="menu__list-item-collapsible"><a class="menu__link menu__link--sublist menu__link--sublist-caret" aria-expanded="false" href="/docs/action/dotnetcore-knife4j-how">ASP.NET Core</a></div></li><li class="theme-doc-sidebar-item-category theme-doc-sidebar-item-category-level-1 menu__list-item"><div class="menu__list-item-collapsible"><a class="menu__link menu__link--sublist menu__link--active" aria-expanded="true" href="/docs/action/springfox">Springfox 源码系列</a><button aria-label="打开/收起侧边栏菜单「Springfox 源码系列」" type="button" class="clean-btn menu__caret"></button></div><ul style="display:block;overflow:visible;height:auto" class="menu__list"><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox1">springfox 源码分析(一) 程序入口</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox2">springfox 源码分析(二) 初探mapstruct</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox3">springfox 源码分析(三) 初探Spring Plugin插件系统</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox4">springfox 源码分析(四) 配置类初始化</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link menu__link--active" aria-current="page" tabindex="0" href="/docs/action/springfox/springfox5">springfox 源码分析(五) web配置类Plugin插件的使用</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox6">springfox 源码分析(六) web配置类扫描包作用探索</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox7">springfox 源码分析(七) 文档初始化</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox8">springfox 源码分析(八) 遍历接口获取Model对象</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox9">springfox 源码分析(九) 文档初始化-分组</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox10">springfox 源码分析(十) 遍历接口获取Model对象</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox11">springfox 源码分析(十一) 自定义添加Swagger Models功能实现</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox12">springfox 源码分析(十二) 遍历接口获取ApiDescription集合</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox13">springfox 源码分析(十三) 自定义扩展实现接口的排序</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox14">springfox 源码分析(十四) 归档得到ApiListing接口集合</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox15">springfox 源码分析(十五) 归档得到Documentation文档对象</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox16">springfox 源码分析(十六) 分组接口swagger-resouces</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox17">springfox 源码分析(十七) Swagger2接口文档示例接口api-docs</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox18">springfox 源码分析(十八) 自定义扩展实现分组的排序</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox19">springfox 源码分析(十九) guava库学习</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox20">springfox 源码分析(二十) 自定义扩展实现Map、JSONObject等动态字段显示</a></li><li class="theme-doc-sidebar-item-link theme-doc-sidebar-item-link-level-2 menu__list-item"><a class="menu__link" tabindex="0" href="/docs/action/springfox/springfox21">springfox 源码分析(二十一) 忽略参数Class类型</a></li></ul></li></ul></nav><button type="button" title="收起侧边栏" aria-label="收起侧边栏" class="button button--secondary button--outline collapseSidebarButton_PEFL"><svg width="20" height="20" aria-hidden="true" class="collapseSidebarButtonIcon_kv0_"><g fill="#7a7a7a"><path d="M9.992 10.023c0 .2-.062.399-.172.547l-4.996 7.492a.982.982 0 01-.828.454H1c-.55 0-1-.453-1-1 0-.2.059-.403.168-.551l4.629-6.942L.168 3.078A.939.939 0 010 2.528c0-.548.45-.997 1-.997h2.996c.352 0 .649.18.828.45L9.82 9.472c.11.148.172.347.172.55zm0 0"></path><path d="M19.98 10.023c0 .2-.058.399-.168.547l-4.996 7.492a.987.987 0 01-.828.454h-3c-.547 0-.996-.453-.996-1 0-.2.059-.403.168-.551l4.625-6.942-4.625-6.945a.939.939 0 01-.168-.55 1 1 0 01.996-.997h3c.348 0 .649.18.828.45l4.996 7.492c.11.148.168.347.168.55zm0 0"></path></g></svg></button></div></aside><main class="docMainContainer_gTbr"><div class="container padding-top--md padding-bottom--lg"><div class="row"><div class="col docItemCol_z5aJ"><div class="docItemContainer_c0TR"><article><nav class="theme-doc-breadcrumbs breadcrumbsContainer_Z_bl" aria-label="页面路径"><ul class="breadcrumbs" itemscope="" itemtype="https://schema.org/BreadcrumbList"><li class="breadcrumbs__item"><a aria-label="主页面" class="breadcrumbs__link" href="/"><svg viewBox="0 0 24 24" class="breadcrumbHomeIcon_OVgt"><path d="M10 19v-5h4v5c0 .55.45 1 1 1h3c.55 0 1-.45 1-1v-7h1.7c.46 0 .68-.57.33-.87L12.67 3.6c-.38-.34-.96-.34-1.34 0l-8.36 7.53c-.34.3-.13.87.33.87H5v7c0 .55.45 1 1 1h3c.55 0 1-.45 1-1z" fill="currentColor"></path></svg></a></li><li itemscope="" itemprop="itemListElement" itemtype="https://schema.org/ListItem" class="breadcrumbs__item"><a class="breadcrumbs__link" itemprop="item" href="/docs/action/springfox"><span itemprop="name">Springfox 源码系列</span></a><meta itemprop="position" content="1"></li><li itemscope="" itemprop="itemListElement" itemtype="https://schema.org/ListItem" class="breadcrumbs__item breadcrumbs__item--active"><span class="breadcrumbs__link" itemprop="name">springfox 源码分析(五) web配置类Plugin插件的使用</span><meta itemprop="position" content="2"></li></ul></nav><div class="tocCollapsible_ETCw theme-doc-toc-mobile tocMobile_ITEo"><button type="button" class="clean-btn tocCollapsibleButton_TO0P">本页总览</button></div><div class="theme-doc-markdown markdown"><h1>springfox 源码分析(五) web配置类Plugin插件的使用</h1><p>时间：2019-5-23 14:46:50</p><p>地点：家中</p><h2 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="前言">前言<a class="hash-link" href="#前言" title="标题的直接链接">​</a></h2><p>我们在上一篇文章,通过<code>@EnableSwagger2</code>注解,知道springfox使用开启Plugin注解的配置,注入了很多Plugin的配置类，结合我们第二篇针对<a href="https://www.xiaominfo.com/2019/05/22/springfox-3/" target="_blank" rel="noopener">Spring Plugin的使用文章</a>介绍,该篇主要探索springfox中的各种不同Plugin的具体作用,以及声明了那些方法</p><h2 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="插件">插件<a class="hash-link" href="#插件" title="标题的直接链接">​</a></h2><p>在<code>SpringfoxWebMvcConfiguration</code>配置中,主要涉及了以下Plugin</p><ul><li>DocumentationPlugin</li><li>ApiListingBuilderPlugin</li><li>OperationBuilderPlugin</li><li>ParameterBuilderPlugin</li><li>ExpandedParameterBuilderPlugin</li><li>OperationModelsProviderPlugin</li><li>DefaultsProviderPlugin</li><li>PathDecorator</li><li>ApiListingScannerPlugin</li></ul><p>代码结构一览：</p><p><img loading="lazy" src="/assets/images/plugins-2ed4be87af296406142088e2503ecc2d.png" width="499" height="496" class="img_ev3q"></p><p>plugin中声明的接口,都是为处理contexts上下文中的属性</p><h3 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="documentationplugin">DocumentationPlugin<a class="hash-link" href="#documentationplugin" title="标题的直接链接">​</a></h3><p>先来看<code>DocumentationPlugin</code>的源码</p><div class="language-java codeBlockContainer_Ckt0 theme-code-block" style="--prism-color:#F8F8F2;--prism-background-color:#282A36"><div class="codeBlockContent_biex"><pre tabindex="0" class="prism-code language-java codeBlock_bY9V thin-scrollbar"><code class="codeBlockLines_e6Vv"><span class="token-line" style="color:#F8F8F2"><span class="token plain">public interface DocumentationPlugin extends Plugin&lt;DocumentationType&gt; {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  /**</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @return indicator to determine if the plugin is enabled</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   */</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  boolean isEnabled();</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  DocumentationType getDocumentationType();</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  /**</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * Creates a documentation context based on a given DocumentationContextBuilder</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   *</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @param builder - @see springfox.documentation.spi.service.contexts.DocumentationContextBuilder</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @return context to use for building the documentation</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   */</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  DocumentationContext configure(DocumentationContextBuilder builder);</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  /**</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * Gets the group name for the plugin. This is expected to be unique for each instance of the plugin</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @return group the plugin belongs to</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   */</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  String getGroupName();</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">}</span><br></span></code></pre><div class="buttonGroup__atx"><button type="button" aria-label="复制代码到剪贴板" title="复制" class="clean-btn"><span class="copyButtonIcons_eSgA" aria-hidden="true"><svg class="copyButtonIcon_y97N" viewBox="0 0 24 24"><path d="M19,21H8V7H19M19,5H8A2,2 0 0,0 6,7V21A2,2 0 0,0 8,23H19A2,2 0 0,0 21,21V7A2,2 0 0,0 19,5M16,1H4A2,2 0 0,0 2,3V17H4V3H16V1Z"></path></svg><svg class="copyButtonSuccessIcon_LjdS" viewBox="0 0 24 24"><path d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z"></path></svg></span></button></div></div></div><p>此Plugin使用的分隔符类是<code>DocumentationType</code>,文档类型,在Springfox中声明了三个版本的文档类型，主要是：</p><ul><li>SWAGGER_2:swagger的2.0版本</li><li>SWAGGER_12:Swagger的1.2版本</li><li>SPRING_WEB:springfox项目是由原spring-mvc-swagger项目演变而来,所以这是最早的一个版本</li></ul><p><code>DocumentationPlugin</code>定义了三个方法：</p><ul><li>是否启用</li><li>获取文档类型</li><li>通过文档上下文Builder构建文档上下文对象</li><li>获取分组名称</li></ul><p>那么,他的实现类是谁，我们通过IDEA的编辑器功能能轻松定位到,是Docket类</p><p>来看类图：</p><p><img loading="lazy" src="/assets/images/DocumentationPlugin-296d89fb609c2f0627e3027b935167f0.png" width="662" height="1196" class="img_ev3q"></p><p>由于Docket对象是最终实现类,而我们开发者一般在使用时,都是通过创建Docket的实体对象来注入到Spring的容器中</p><p>所以,我们创建几个Docket对象的Bean实例，那么通过<code>PluginRetry&lt;DocumentationPlugin,DocumentationType&gt;</code>的getPlugins()方法,最终就会获取到外部注入的Docket对象实例,然后再程序中就可以使用了</p><h3 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="apilistingbuilderplugin">ApiListingBuilderPlugin<a class="hash-link" href="#apilistingbuilderplugin" title="标题的直接链接">​</a></h3><p>来看<code>ApiListingBuilderPlugin</code>的源码</p><div class="language-java codeBlockContainer_Ckt0 theme-code-block" style="--prism-color:#F8F8F2;--prism-background-color:#282A36"><div class="codeBlockContent_biex"><pre tabindex="0" class="prism-code language-java codeBlock_bY9V thin-scrollbar"><code class="codeBlockLines_e6Vv"><span class="token-line" style="color:#F8F8F2"><span class="token plain">public interface ApiListingBuilderPlugin extends Plugin&lt;DocumentationType&gt; {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  /**</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * Implement this method to override the ApiListing using the ApiListingBuilder</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   *</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @param apiListingContext - context that can be used to override the model property attributes</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @see springfox.documentation.service.ApiListing</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @see springfox.documentation.builders.ApiListingBuilder</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   */</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  void apply(ApiListingContext apiListingContext);</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">}</span><br></span></code></pre><div class="buttonGroup__atx"><button type="button" aria-label="复制代码到剪贴板" title="复制" class="clean-btn"><span class="copyButtonIcons_eSgA" aria-hidden="true"><svg class="copyButtonIcon_y97N" viewBox="0 0 24 24"><path d="M19,21H8V7H19M19,5H8A2,2 0 0,0 6,7V21A2,2 0 0,0 8,23H19A2,2 0 0,0 21,21V7A2,2 0 0,0 19,5M16,1H4A2,2 0 0,0 2,3V17H4V3H16V1Z"></path></svg><svg class="copyButtonSuccessIcon_LjdS" viewBox="0 0 24 24"><path d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z"></path></svg></span></button></div></div></div><p>实现<code>ApiListingBuilderPlugin</code>插件类需要实现apply方法,主要是处理ApiListingContext上下文的属性信息</p><p>来看类图：</p><p><img loading="lazy" src="/assets/images/ApiListingBuilderPlugin-3b2dd7465b8850f0b50cc20db42d9a54.png" width="1131" height="535" class="img_ev3q"></p><p>从<code>ApiListingBuilderPlugin</code>类图中,我们可以看到,他有三个子类,分别是：</p><ul><li>MediaTypeReader：获取接口的<code>RequestMapping</code>注解,赋值Produces和Consumes属性</li><li>ApiListingReader：针对controller名称的处理操作,最后赋值给ApiListingBuilder对象description属性</li><li>SwaggerApiListingReader:获取@Api注解,赋值tag及description属性</li></ul><p>这三个实现类都通过<code>@Component</code>注解注入到了Spring的容器中</p><h3 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="operationbuilderplugin">OperationBuilderPlugin<a class="hash-link" href="#operationbuilderplugin" title="标题的直接链接">​</a></h3><p>springfox中的一些列插件Plugin最终的作用都是分别为定义传参的Context上下文进行一系列的赋值处理</p><p>每个上下文中几乎都会存在该对象的Builder,最终通过各种不同的Plugin来分别进行赋值,这样整个程序架构会清晰很多</p><p><code>Operation</code>也不例外,先来看Operation的上下文类</p><p><code>OperationContext.java</code></p><div class="language-java codeBlockContainer_Ckt0 theme-code-block" style="--prism-color:#F8F8F2;--prism-background-color:#282A36"><div class="codeBlockContent_biex"><pre tabindex="0" class="prism-code language-java codeBlock_bY9V thin-scrollbar"><code class="codeBlockLines_e6Vv"><span class="token-line" style="color:#F8F8F2"><span class="token plain">public class OperationContext {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    //builder函数</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  private final OperationBuilder operationBuilder;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    //Spring中接口的请求方法类型枚举</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  private final RequestMethod requestMethod;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    //请求接口上下文</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  private final RequestMappingContext requestContext;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  private final int operationIndex;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    //getter setter and constructor</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    </span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">}</span><br></span></code></pre><div class="buttonGroup__atx"><button type="button" aria-label="复制代码到剪贴板" title="复制" class="clean-btn"><span class="copyButtonIcons_eSgA" aria-hidden="true"><svg class="copyButtonIcon_y97N" viewBox="0 0 24 24"><path d="M19,21H8V7H19M19,5H8A2,2 0 0,0 6,7V21A2,2 0 0,0 8,23H19A2,2 0 0,0 21,21V7A2,2 0 0,0 19,5M16,1H4A2,2 0 0,0 2,3V17H4V3H16V1Z"></path></svg><svg class="copyButtonSuccessIcon_LjdS" viewBox="0 0 24 24"><path d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z"></path></svg></span></button></div></div></div><p>此时,我们来看<code>OperationBuilderPlugin</code>插件的源码：</p><div class="language-java codeBlockContainer_Ckt0 theme-code-block" style="--prism-color:#F8F8F2;--prism-background-color:#282A36"><div class="codeBlockContent_biex"><pre tabindex="0" class="prism-code language-java codeBlock_bY9V thin-scrollbar"><code class="codeBlockLines_e6Vv"><span class="token-line" style="color:#F8F8F2"><span class="token plain">public interface OperationBuilderPlugin extends Plugin&lt;DocumentationType&gt; {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  /**</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * Implement this method to override the Operation using the OperationBuilder available in the context</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   *</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @param context - context that can be used to override the parameter attributes</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @see springfox.documentation.service.Operation</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @see springfox.documentation.builders.OperationBuilder</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   */</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  void apply(OperationContext context);</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">}</span><br></span></code></pre><div class="buttonGroup__atx"><button type="button" aria-label="复制代码到剪贴板" title="复制" class="clean-btn"><span class="copyButtonIcons_eSgA" aria-hidden="true"><svg class="copyButtonIcon_y97N" viewBox="0 0 24 24"><path d="M19,21H8V7H19M19,5H8A2,2 0 0,0 6,7V21A2,2 0 0,0 8,23H19A2,2 0 0,0 21,21V7A2,2 0 0,0 19,5M16,1H4A2,2 0 0,0 2,3V17H4V3H16V1Z"></path></svg><svg class="copyButtonSuccessIcon_LjdS" viewBox="0 0 24 24"><path d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z"></path></svg></span></button></div></div></div><p>顶级Plugin声明接口,分层逐步给OperationContext对象赋值</p><p>先来看部分类图：</p><p><img loading="lazy" src="/assets/images/OperationBuilderPlugin-aac79ea43ebfb63cbaaeca149e3e9047.png" width="1552" height="1135" class="img_ev3q"></p><p>由于<code>OperationBuilderPlugin</code>实现类比较多,此处类图进列出其中四个实现类,我们通过文字来一一说明</p><ul><li><code>DefaultOperationReader</code>:请求方法、接口说明、唯一id值</li><li><code>MediaTypeReader</code>:consumes、produces</li><li><code>OperationAuthReader</code>:权限赋值</li><li><code>OperationDeprecatedReader</code>；接口是否过时</li><li><code>OperationHiddenReader</code>：是否隐藏</li><li><code>OperationHttpMethodReader</code>:接口请求方法</li><li><code>OperationImplicitParameterReader</code>:针对<code>@ApiImplicitParam</code>注解的接口进行读取赋值</li><li><code>OperationImplicitParametersReader</code>:针对<code>@ApiImplicitParams</code>注解的接口进行读取赋值</li><li><code>OperationNicknameIntoUniqueIdReader</code>:昵称属性,通过读取<code>@ApiOperation</code>注解中的<code>nickname</code>属性进行赋值</li><li><code>OperationNotesReader</code>:接口说明</li><li><code>OperationParameterHeadersConditionReader</code>:请求头</li><li><code>OperationParameterReader</code>:后端配置的全局parameter以及接口的parameter参数进行读取赋值</li><li><code>OperationParameterRequestConditionReader</code>:参数条件</li><li><code>OperationPositionReader</code>:position属性</li><li><code>OperationResponseClassReader</code>:响应类处理</li><li><code>OperationSummaryReader</code>:接口名称</li><li><code>OperationTagsReader</code>:tags</li><li><code>ResponseMessagesReader</code>:响应状态码信息，先读取后端配置的全局,然后读取接口</li><li><code>SwaggerMediaTypeReader</code>:consumes、produces</li><li><code>SwaggerOperationResponseClassReader</code>:响应class类</li><li><code>SwaggerOperationTagsReader</code>：接口的tags处理</li><li><code>SwaggerResponseMessageReader</code>:状态码信息,针对<code>@ApiResponse</code>注解标注的接口</li><li><code>VendorExtensionsReader</code>:扩展</li></ul><p>整个代码结构一览：</p><p><img loading="lazy" src="/assets/images/scan-5695bd9104e24c9d3380ceafbacbc43e.png" width="501" height="526" class="img_ev3q"></p><h3 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="parameterbuilderplugin">ParameterBuilderPlugin<a class="hash-link" href="#parameterbuilderplugin" title="标题的直接链接">​</a></h3><p>针对参数处理的Plugin，先来看相关类图：</p><p><img loading="lazy" src="/assets/images/ParameterBuilderPlugin-13a40644ea5704cfddb3055f56f6482c.png" width="2984" height="590" class="img_ev3q"></p><p>总共有七个实现类，我们一一说明：</p><ul><li><code>ApiParamParameterBuilder</code>:针对接口使用<code>@ApiParam</code>注解的参数进行处理</li><li><code>ParameterDataTypeReader</code>:参数的数据类型</li><li><code>ParameterDefaultReader</code>:参数默认值</li><li><code>ParameterMultiplesReader</code>:</li><li><code>ParameterNameReader</code>:参数名称</li><li><code>ParameterRequiredReader</code>:参数是否必须</li><li><code>ParameterTypeReader</code>：参数类型，包括（form、header、query、formdata、body），默认是body</li></ul><h3 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="expandedparameterbuilderplugin">ExpandedParameterBuilderPlugin<a class="hash-link" href="#expandedparameterbuilderplugin" title="标题的直接链接">​</a></h3><p>先来看类图关系</p><p><img loading="lazy" src="/assets/images/ExpandedParameterBuilderPlugin-174445ad55b48a496a3d6443d6933f0a.png" width="1042" height="719" class="img_ev3q"></p><p>从类图关系中,实现类主要有两个：</p><ul><li><code>ExpandedParameterBuilder</code>:实体类参数的默认属性赋值</li><li><code>SwaggerExpandedParameterBuilder</code>:针对我们的类使用<code>@ApiModelProperty</code>注解的操作</li></ul><h3 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="operationmodelsproviderplugin">OperationModelsProviderPlugin<a class="hash-link" href="#operationmodelsproviderplugin" title="标题的直接链接">​</a></h3><p>来看类图关系</p><p><img loading="lazy" src="/assets/images/OperationModelsProviderPlugin-2c0b8506e1c2be1b7dbaa6e4c3281961.png" width="1044" height="1049" class="img_ev3q"></p><ul><li><code>OperationModelsProvider</code>:收集所有的参数Models,返回类型，全局Models</li><li><code>SwaggerOperationModelsProvider</code>:接口返回类型已经使用<code>@ApiResponse</code>标注的返回类型</li></ul><h3 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="defaultsproviderplugin">DefaultsProviderPlugin<a class="hash-link" href="#defaultsproviderplugin" title="标题的直接链接">​</a></h3><p>来看<code>DefaultsProviderPlugin</code>的源码</p><div class="language-java codeBlockContainer_Ckt0 theme-code-block" style="--prism-color:#F8F8F2;--prism-background-color:#282A36"><div class="codeBlockContent_biex"><pre tabindex="0" class="prism-code language-java codeBlock_bY9V thin-scrollbar"><code class="codeBlockLines_e6Vv"><span class="token-line" style="color:#F8F8F2"><span class="token plain">public interface DefaultsProviderPlugin extends Plugin&lt;DocumentationType&gt; {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  /**</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * Implement this method to override the @see  springfox.documentation.spi.service.contexts</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * .DocumentationContextBuilder</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   *</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @param documentationType - creates a default DocumentationContextBuilder based on documentation type</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @return - returns the documentation context builder</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   */</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  DocumentationContextBuilder create(DocumentationType documentationType);</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">}</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span></code></pre><div class="buttonGroup__atx"><button type="button" aria-label="复制代码到剪贴板" title="复制" class="clean-btn"><span class="copyButtonIcons_eSgA" aria-hidden="true"><svg class="copyButtonIcon_y97N" viewBox="0 0 24 24"><path d="M19,21H8V7H19M19,5H8A2,2 0 0,0 6,7V21A2,2 0 0,0 8,23H19A2,2 0 0,0 21,21V7A2,2 0 0,0 19,5M16,1H4A2,2 0 0,0 2,3V17H4V3H16V1Z"></path></svg><svg class="copyButtonSuccessIcon_LjdS" viewBox="0 0 24 24"><path d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z"></path></svg></span></button></div></div></div><p>根据文档类型创建<code>DocumentationContextBuilder</code>对象</p><p>而<code>DefaultsProviderPlugin</code>只有一个实现子类,那就是<code>springfox.documentation.spring.web.plugins.DefaultConfiguration</code></p><div class="language-java codeBlockContainer_Ckt0 theme-code-block" style="--prism-color:#F8F8F2;--prism-background-color:#282A36"><div class="codeBlockContent_biex"><pre tabindex="0" class="prism-code language-java codeBlock_bY9V thin-scrollbar"><code class="codeBlockLines_e6Vv"><span class="token-line" style="color:#F8F8F2"><span class="token plain">public class DefaultConfiguration implements DefaultsProviderPlugin {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  private final Defaults defaults;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  private final TypeResolver typeResolver;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  private final ServletContext servletContext;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  public DefaultConfiguration(Defaults defaults,</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">                       TypeResolver typeResolver,</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">                       ServletContext servletContext) {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    this.servletContext = servletContext;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    this.defaults = defaults;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    this.typeResolver = typeResolver;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  }</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  @Override</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  public DocumentationContextBuilder create(DocumentationType documentationType) {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    return new DocumentationContextBuilder(documentationType)</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .operationOrdering(defaults.operationOrdering())</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .apiDescriptionOrdering(defaults.apiDescriptionOrdering())</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .apiListingReferenceOrdering(defaults.apiListingReferenceOrdering())</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .additionalIgnorableTypes(defaults.defaultIgnorableParameterTypes())</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .rules(defaults.defaultRules(typeResolver))</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .defaultResponseMessages(defaults.defaultResponseMessages())</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .pathProvider(new RelativePathProvider(servletContext))</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .typeResolver(typeResolver)</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .enableUrlTemplating(false)</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">            .selector(ApiSelector.DEFAULT);</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  }</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  @Override</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  public boolean supports(DocumentationType delimiter) {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">    return true;</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  }</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">}</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span></code></pre><div class="buttonGroup__atx"><button type="button" aria-label="复制代码到剪贴板" title="复制" class="clean-btn"><span class="copyButtonIcons_eSgA" aria-hidden="true"><svg class="copyButtonIcon_y97N" viewBox="0 0 24 24"><path d="M19,21H8V7H19M19,5H8A2,2 0 0,0 6,7V21A2,2 0 0,0 8,23H19A2,2 0 0,0 21,21V7A2,2 0 0,0 19,5M16,1H4A2,2 0 0,0 2,3V17H4V3H16V1Z"></path></svg><svg class="copyButtonSuccessIcon_LjdS" viewBox="0 0 24 24"><path d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z"></path></svg></span></button></div></div></div><p>给DocumentationContextBuilder创建一系列空对象默认值,方便后期其他Plugin进行赋值初始化</p><p><code>Defaults</code>和<code>TypeResolver</code>在前面的Configuration配置类中已经通过Bean注解进行了注入</p><h3 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="pathdecorator">PathDecorator<a class="hash-link" href="#pathdecorator" title="标题的直接链接">​</a></h3><p>先来看类图：</p><p><img loading="lazy" src="/assets/images/PathDecorator-cd5dfccca4ea54760bdf9c3666d63f4a.png" width="1516" height="506" class="img_ev3q"></p><p><code>PathDecorator</code>声明了一个Guava函数库中的Function函数接口</p><p><code>Function</code></p><div class="language-java codeBlockContainer_Ckt0 theme-code-block" style="--prism-color:#F8F8F2;--prism-background-color:#282A36"><div class="codeBlockContent_biex"><pre tabindex="0" class="prism-code language-java codeBlock_bY9V thin-scrollbar"><code class="codeBlockLines_e6Vv"><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">@GwtCompatible</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">public interface Function&lt;F, T&gt; {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  @Nullable</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  @CanIgnoreReturnValue // TODO(kevinb): remove this</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  T apply(@Nullable F input);</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  /**</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * &lt;i&gt;May&lt;/i&gt; return {@code true} if {@object} is a {@code Function} that behaves identically to</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * this function.</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   *</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * &lt;p&gt;&lt;b&gt;Warning: do not depend&lt;/b&gt; on the behavior of this method.</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   *</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * &lt;p&gt;Historically, {@code Function} instances in this library have implemented this method to</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * recognize certain cases where distinct {@code Function} instances would in fact behave</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * identically. However, as code migrates to {@code java.util.function}, that behavior will</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * disappear. It is best not to depend on it.</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   */</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  @Override</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  boolean equals(@Nullable Object object);</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">}</span><br></span></code></pre><div class="buttonGroup__atx"><button type="button" aria-label="复制代码到剪贴板" title="复制" class="clean-btn"><span class="copyButtonIcons_eSgA" aria-hidden="true"><svg class="copyButtonIcon_y97N" viewBox="0 0 24 24"><path d="M19,21H8V7H19M19,5H8A2,2 0 0,0 6,7V21A2,2 0 0,0 8,23H19A2,2 0 0,0 21,21V7A2,2 0 0,0 19,5M16,1H4A2,2 0 0,0 2,3V17H4V3H16V1Z"></path></svg><svg class="copyButtonSuccessIcon_LjdS" viewBox="0 0 24 24"><path d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z"></path></svg></span></button></div></div></div><p>传入输入参数,返回输出参数</p><p>主要实现类：</p><ul><li><code>OperationPathDecorator</code>:basePath处理类</li><li><code>PathMappingDecorator</code>:接口path处理</li><li><code>PathSanitizer</code>:接口path-origin处理</li><li><code>QueryStringUriTemplateDecorator</code>:接口参数处理</li></ul><h3 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="apilistingscannerplugin">ApiListingScannerPlugin<a class="hash-link" href="#apilistingscannerplugin" title="标题的直接链接">​</a></h3><p>来看源码</p><div class="language-java codeBlockContainer_Ckt0 theme-code-block" style="--prism-color:#F8F8F2;--prism-background-color:#282A36"><div class="codeBlockContent_biex"><pre tabindex="0" class="prism-code language-java codeBlock_bY9V thin-scrollbar"><code class="codeBlockLines_e6Vv"><span class="token-line" style="color:#F8F8F2"><span class="token plain">public interface ApiListingScannerPlugin extends Plugin&lt;DocumentationType&gt; {</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  /**</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * Implement this method to manually add ApiDescriptions</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   *</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @param context - Documentation context that can be used infer documentation context</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @see springfox.documentation.service.ApiDescription</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   * @return List of {@link ApiDescription}</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">   */</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">  List&lt;ApiDescription&gt; apply(DocumentationContext context);</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain">}</span><br></span><span class="token-line" style="color:#F8F8F2"><span class="token plain" style="display:inline-block"></span><br></span></code></pre><div class="buttonGroup__atx"><button type="button" aria-label="复制代码到剪贴板" title="复制" class="clean-btn"><span class="copyButtonIcons_eSgA" aria-hidden="true"><svg class="copyButtonIcon_y97N" viewBox="0 0 24 24"><path d="M19,21H8V7H19M19,5H8A2,2 0 0,0 6,7V21A2,2 0 0,0 8,23H19A2,2 0 0,0 21,21V7A2,2 0 0,0 19,5M16,1H4A2,2 0 0,0 2,3V17H4V3H16V1Z"></path></svg><svg class="copyButtonSuccessIcon_LjdS" viewBox="0 0 24 24"><path d="M21,7L9,19L3.5,13.5L4.91,12.09L9,16.17L19.59,5.59L21,7Z"></path></svg></span></button></div></div></div><p>该Plugin没有任何实现子类</p><h2 class="anchor anchorWithHideOnScrollNavbar_WYt5" id="总结">总结<a class="hash-link" href="#总结" title="标题的直接链接">​</a></h2><p>通过上面的Plugin,我们大致了解了Springfox中定义的Plugin接口,以及实现类,完事具备，此时只需要查看springfox的初始化代码部分了</p><p>在下一篇文章中我们继续.</p></div><footer class="theme-doc-footer docusaurus-mt-lg"><div class="theme-doc-footer-edit-meta-row row"><div class="col"></div><div class="col lastUpdated_vwxv"><span class="theme-last-updated">最后<!-- -->由 <b>xiaoyumin</b> <!-- -->于 <b><time datetime="2022-08-15T15:32:11.000Z">2022年8月15日</time></b> <!-- -->更新</span></div></div></footer></article><nav class="pagination-nav docusaurus-mt-lg" aria-label="文档分页导航"><a class="pagination-nav__link pagination-nav__link--prev" href="/docs/action/springfox/springfox4"><div class="pagination-nav__sublabel">上一页</div><div class="pagination-nav__label">springfox 源码分析(四) 配置类初始化</div></a><a class="pagination-nav__link pagination-nav__link--next" href="/docs/action/springfox/springfox6"><div class="pagination-nav__sublabel">下一页</div><div class="pagination-nav__label">springfox 源码分析(六) web配置类扫描包作用探索</div></a></nav></div></div><div class="col col--3"><div class="tableOfContents_bqdL thin-scrollbar theme-doc-toc-desktop"><ul class="table-of-contents table-of-contents__left-border"><li><a href="#前言" class="table-of-contents__link toc-highlight">前言</a></li><li><a href="#插件" class="table-of-contents__link toc-highlight">插件</a><ul><li><a href="#documentationplugin" class="table-of-contents__link toc-highlight">DocumentationPlugin</a></li><li><a href="#apilistingbuilderplugin" class="table-of-contents__link toc-highlight">ApiListingBuilderPlugin</a></li><li><a href="#operationbuilderplugin" class="table-of-contents__link toc-highlight">OperationBuilderPlugin</a></li><li><a href="#parameterbuilderplugin" class="table-of-contents__link toc-highlight">ParameterBuilderPlugin</a></li><li><a href="#expandedparameterbuilderplugin" class="table-of-contents__link toc-highlight">ExpandedParameterBuilderPlugin</a></li><li><a href="#operationmodelsproviderplugin" class="table-of-contents__link toc-highlight">OperationModelsProviderPlugin</a></li><li><a href="#defaultsproviderplugin" class="table-of-contents__link toc-highlight">DefaultsProviderPlugin</a></li><li><a href="#pathdecorator" class="table-of-contents__link toc-highlight">PathDecorator</a></li><li><a href="#apilistingscannerplugin" class="table-of-contents__link toc-highlight">ApiListingScannerPlugin</a></li></ul></li><li><a href="#总结" class="table-of-contents__link toc-highlight">总结</a></li></ul></div></div></div></div></main></div></div><footer class="footer"><div class="container container-fluid"><div class="row footer__links"><div class="col footer__col"><div class="footer__title">文档指南</div><ul class="footer__items clean-list"><li class="footer__item"><a class="footer__link-item" href="/docs/quick-start">文档</a></li><li class="footer__item"><a class="footer__link-item" href="/docs/community/simple-demo">示例</a></li><li class="footer__item"><a class="footer__link-item" href="/docs/changelog">更新日志</a></li><li class="footer__item"><a class="footer__link-item" href="/docs/upgrading/upgrading-to-v4">升级到v4.0</a></li></ul></div><div class="col footer__col"><div class="footer__title">社区</div><ul class="footer__items clean-list"><li class="footer__item"><a href="https://gitter.im/knife4j/knife4j" target="_blank" rel="noopener noreferrer" class="footer__link-item">Gitter<svg width="13.5" height="13.5" aria-hidden="true" viewBox="0 0 24 24" class="iconExternalLink_nPIU"><path fill="currentColor" d="M21 13v10h-21v-19h12v2h-10v15h17v-8h2zm3-12h-10.988l4.035 4-6.977 7.07 2.828 2.828 6.977-7.07 4.125 4.172v-11z"></path></svg></a></li><li class="footer__item"><a href="https://www.oschina.net/question/tag/swagger-bootstrap-ui" target="_blank" rel="noopener noreferrer" class="footer__link-item">开源中国<svg width="13.5" height="13.5" aria-hidden="true" viewBox="0 0 24 24" class="iconExternalLink_nPIU"><path fill="currentColor" d="M21 13v10h-21v-19h12v2h-10v15h17v-8h2zm3-12h-10.988l4.035 4-6.977 7.07 2.828 2.828 6.977-7.07 4.125 4.172v-11z"></path></svg></a></li></ul></div><div class="col footer__col"><div class="footer__title">关注公众号</div><ul class="footer__items clean-list"><li class="footer__item"><img src="/images/website/qrcode.jpg" width="150"></li></ul></div><div class="col footer__col"><div class="footer__title">更多</div><ul class="footer__items clean-list"><li class="footer__item"><a href="https://docusaurus.io" target="_blank" rel="noopener noreferrer" class="footer__link-item">Docusaurus<svg width="13.5" height="13.5" aria-hidden="true" viewBox="0 0 24 24" class="iconExternalLink_nPIU"><path fill="currentColor" d="M21 13v10h-21v-19h12v2h-10v15h17v-8h2zm3-12h-10.988l4.035 4-6.977 7.07 2.828 2.828 6.977-7.07 4.125 4.172v-11z"></path></svg></a></li><li class="footer__item"><a href="https://gitee.com/xiaoym/knife4j" target="_blank" rel="noopener noreferrer" class="footer__link-item">Gitee<svg width="13.5" height="13.5" aria-hidden="true" viewBox="0 0 24 24" class="iconExternalLink_nPIU"><path fill="currentColor" d="M21 13v10h-21v-19h12v2h-10v15h17v-8h2zm3-12h-10.988l4.035 4-6.977 7.07 2.828 2.828 6.977-7.07 4.125 4.172v-11z"></path></svg></a></li><li class="footer__item"><a href="https://github.com/xiaoymin/swagger-bootstrap-ui" target="_blank" rel="noopener noreferrer" class="footer__link-item">GitHub<svg width="13.5" height="13.5" aria-hidden="true" viewBox="0 0 24 24" class="iconExternalLink_nPIU"><path fill="currentColor" d="M21 13v10h-21v-19h12v2h-10v15h17v-8h2zm3-12h-10.988l4.035 4-6.977 7.07 2.828 2.828 6.977-7.07 4.125 4.172v-11z"></path></svg></a></li></ul></div></div><div class="footer__bottom text--center"><div class="footer__copyright">Apache License 2.0 | Copyright © 2018-2023-八一菜刀 浙ICP备18027673号-1 </div></div></div></footer></div>
<script src="/assets/js/runtime~main.e0db172c.js"></script>
<script src="/assets/js/main.c059fb6e.js"></script>
<!-- Google Tag Manager (noscript) -->
    <noscript><iframe src="https://www.googletagmanager.com/ns.html?id=GTM-TKBX678" height="0" width="0" style="display:none;visibility:hidden"></iframe></noscript>
    <!-- End Google Tag Manager (noscript) --></body>
</html>